home *** CD-ROM | disk | FTP | other *** search
- /*
- File: Buffer.h
-
- Copyright: © 1991-1994 by Apple Computer, Inc.
- All rights reserved.
-
- Part of the AOCE Sample SMSAM Package. Consult the license
- which came with this software for your specific legal rights.
-
- */
-
-
-
- #ifndef __BUFFER__
- #define __BUFFER__
-
- #ifndef __MEMORY__
- #include "Memory.h"
- #endif
-
- #ifndef __DIRECTOBJECT__
- #include "DirectObject.h"
- #endif
-
- #pragma push
- #pragma segment Buffer
-
- class ostream;
- class ABuffer;
-
- extern short CompareBuffers ( const void* a, unsigned long alen, const void* b, unsigned long blen );
- inline unsigned long Minimum ( unsigned long a, unsigned long b ) { return a < b ? a : b; }
-
- /*============================================================================
-
- ABuffer is a abstract class representing a buffer, a chunk of
- contiguous RAM which has a physical length and a starting address.
-
- ----------------------------------------------------------------------------*/
-
- class ABuffer : public TDirectObject
- {
- public:
-
- virtual ~ABuffer ();
- ABuffer& operator = ( const ABuffer& );
-
- operator const void* () const;
-
- // subclasses must implement these…
- virtual const void* GetPhysicalStart () const = 0;
- virtual unsigned long SetPhysicalLength ( unsigned long ) = 0;
- virtual unsigned long GetPhysicalLength () const = 0;
-
- // comparison methods
- virtual Boolean operator == ( const ABuffer& ) const;
- virtual Boolean operator != ( const ABuffer& ) const;
-
- // safe copying methods
- virtual unsigned long ReadFrom ( const void* source, unsigned long length );
- virtual unsigned long WriteTo ( void* dest, unsigned long length ) const;
-
- // content setting methods
- virtual void ZeroBuffer ();
- virtual void FillBuffer ( unsigned char );
-
- // debugging
- virtual ostream& operator >> ( ostream& ) const;
-
- protected: ABuffer ();
- };
-
- /*============================================================================
-
- CBuffer is a concrete class representing a buffer.
-
- The implementation of this class is smart; i.e. if the buffer logical
- length is no greater than 7 bytes, then the buffer data is stored
- inside the object, that keeps us from senselessly allocating teensy
- blocks on the heap since we have space in the object already.
-
- ----------------------------------------------------------------------------*/
-
- class CBuffer : public ABuffer
- {
- public: CBuffer ();
- CBuffer ( unsigned long length );
- CBuffer ( const void* source, unsigned long length );
- CBuffer ( const ABuffer& );
- CBuffer ( const CBuffer& );
- virtual ~CBuffer ();
- CBuffer& operator = ( const CBuffer& );
-
- virtual const void* GetPhysicalStart () const;
- virtual unsigned long SetPhysicalLength ( unsigned long );
- virtual unsigned long GetPhysicalLength () const;
-
- virtual ostream& operator >> ( ostream& ) const;
-
- private:
- unsigned char fIsExternal;
-
- struct External
- {
- unsigned long fLength;
- void* fBuffer;
- };
-
- #define kBufferMaxInternalLength ( sizeof ( External ) - sizeof ( unsigned char ) )
-
- struct Internal
- {
- unsigned char fLength;
- unsigned char fBuffer [ kBufferMaxInternalLength ];
- };
-
- union
- {
- External fExternal;
- Internal fInternal;
- } fType;
- };
-
- /*============================================================================
-
- CPrefixBuffer is a concrete class which represents a buffer
- which creates a new buffer containing a length prefix from an existing
- buffer. The length prefix can be a 1, 2, or 4 byte unsigned integer.
-
- The length prefix buffer will be larger than the original buffer by
- either 1, 2, or 4 bytes, and this prefix will contain an unsigned
- integer representing the length of the original buffer.
-
- When the length buffer is destructed, it can also write its contents
- back to the original buffer, this option is selected in the constructor
- argument list parameter “updateSource”.
-
- For example, this class can be used to easily create a pascal string
- copy of a null terminated string:
-
- char s [] = "Hello World!!";
- CPrefixBuffer b ( s, strlen ( s ), sizeof ( char ) );
- char* t = (char*) b.GetPhysicalStart ();
-
- The data pointed to by <t> would look like:
-
- $0C $48 $65 $6c $6c $6f $20 $57 $6f $72 $6c $64 $21 $21
- ‘\n’ ‘H’ ‘e’ ‘l’ ‘l’ ‘o’ ‘ ’ ‘W’ ‘o’ ‘r’ ‘l’ ‘d’ ‘!’ ‘!’
-
- ----------------------------------------------------------------------------*/
-
- class CPrefixBuffer : public ABuffer
- {
- public:
-
- enum Prefix { kByte = 1, kWord = 2, kLong = 4 };
-
- CPrefixBuffer ( const ABuffer&, Prefix = kByte );
- CPrefixBuffer ( ABuffer&, Boolean update, Prefix = kByte );
- CPrefixBuffer ( const void*, unsigned long, Prefix = kByte );
- CPrefixBuffer ( Prefix, unsigned long logicalSize );
- virtual ~CPrefixBuffer ();
-
- virtual const void* GetLogicalStart () const;
- virtual unsigned long SetLogicalLength ( unsigned long );
- virtual unsigned long GetLogicalLength () const;
-
- virtual const void* GetPhysicalStart () const;
- virtual unsigned long SetPhysicalLength ( unsigned long );
- virtual unsigned long GetPhysicalLength () const;
-
- virtual void SetSource ( ABuffer* );
- const ABuffer* GetSource () const;
-
- virtual void SetUpdate ( Boolean );
- Boolean GetUpdate () const;
- virtual unsigned long UpdateNow ();
-
- virtual ostream& operator >> ( ostream& ) const;
-
- protected: void UpdatePrefixWithLength ( unsigned long logicalLength );
-
- private: CBuffer fBuffer;
- ABuffer* fSource;
- Prefix fPrefix;
- Boolean fUpdate;
- };
-
- /*============================================================================
-
- CWrapperBuffer is a concrete buffer class which wraps a non-object
- chunk of nonrelocatable memory.
-
- ----------------------------------------------------------------------------*/
-
- class CWrapperBuffer : public ABuffer
- {
- public: CWrapperBuffer ( void* source, unsigned long length );
- virtual ~CWrapperBuffer ();
-
- virtual const void* GetPhysicalStart () const;
- virtual unsigned long SetPhysicalLength ( unsigned long );
- virtual unsigned long GetPhysicalLength () const;
-
- private: void* fSource;
- unsigned long fLength;
- };
-
- /***********************************|****************************************/
-
- inline ABuffer::operator const void* () const { return GetPhysicalStart (); }
- inline void ABuffer::ZeroBuffer () { FillBuffer ( 0 ); }
- inline Boolean ABuffer::operator != ( const ABuffer& that ) const { return !operator == ( that ); }
- inline const void* CBuffer::GetPhysicalStart () const { return fIsExternal ? fType.fExternal.fBuffer : fType.fInternal.fBuffer; }
- inline unsigned long CBuffer::GetPhysicalLength () const { return fIsExternal ? fType.fExternal.fLength : fType.fInternal.fLength; }
- inline const void* CPrefixBuffer::GetPhysicalStart () const { return fBuffer.GetPhysicalStart (); }
- inline const void* CPrefixBuffer::GetLogicalStart () const { return (char*) fBuffer.GetPhysicalStart () + fPrefix; }
- inline unsigned long CPrefixBuffer::GetPhysicalLength () const { return fBuffer.GetPhysicalLength (); }
- inline unsigned long CPrefixBuffer::SetPhysicalLength ( unsigned long length ) { return fBuffer.SetPhysicalLength ( length ); }
- inline void CPrefixBuffer::SetSource ( ABuffer* source ) { fSource = source; }
- inline const ABuffer* CPrefixBuffer::GetSource () const { return fSource; }
- inline void CPrefixBuffer::SetUpdate ( Boolean update ) { fUpdate = update; }
- inline Boolean CPrefixBuffer::GetUpdate () const { return fUpdate; }
- inline const void* CWrapperBuffer::GetPhysicalStart () const { return fSource; }
- inline unsigned long CWrapperBuffer::GetPhysicalLength () const { return fLength; }
-
- /***********************************|****************************************/
-
- #pragma pop
-
- #endif // __BUFFER__
-